#include "stdafx.h"
#include "HistoryGraph.h"

#pragma warning (disable : 4244)

SmartPtr <System_HistoryGraph> g_pSystem_HistoryGraph;

System_HistoryGraph :: 
GraphRecrod :: GraphRecrod(int Size, COLOR Color, Vector & Position) : mColor(Color)
{
	mPos = 0;
	mVertices.assign(Size, hgeVertex());
	int xStart = -(Size >> 1);
	for(int i = Size - 1; i != -1; i--)
	{
		mVertices[i].x = xStart + i + Position.x;
		mVertices[i].y = Position.y;
		mVertices[i].z = 0.0f;
		mVertices[i].col = ARGB(255, 255, 255, 255);
		mVertices[i].tx = mVertices[i].ty = 0.0f;
	}
}

System_HistoryGraph::
GraphRecrod :: ~GraphRecrod()
{
}

void System_HistoryGraph::
GraphRecrod :: AddPoint(const float & Point)
{	
	mVertices.back().y = Point;
	for(size_t i = 0; i < mVertices.size() - 1; i++)
		mVertices[i].y = mVertices[i + 1].y; 
	//mVertices[mPos].y = Point;
	//(static_cast<unsigned int>(++mPos) < mVertices.size())? NULL : mPos = 0;
}


System_HistoryGraph :: System_HistoryGraph()
: Console_Subscriber("System_Graph"), mPosition(), mbActive(false)
{
	mWindowView.x1 = mWindowView.y1 = 0.0f;
	mPosition.x = -(APP_WIDTH >> 1) + (300 >> 1);
	mPosition.y = (APP_HEIGHT >> 1) - (200 >> 1); 

	SetDimension(300, 200);
	mLineHighLightMin = AddLine(0, ARGB(255, 0, 0, 255));
	mLineHighLightMax = AddLine(0, ARGB(255, 255, 0, 0));
	AddGraph(ARGB(255, 255, 255, 255));

	SetHighLights(-50, 100);
	EnableScaling(true);
	ShowHighLightsLimit(true);
}

System_HistoryGraph :: ~System_HistoryGraph()
{
}

void System_HistoryGraph :: EnableScaling(const bool & OnOff)
{
	mFlags &= ~1;
	mFlags |= (OnOff)? 1 : 0;
	SetLine(mLineHighLightMin, mfHighLightMin);
	SetLine(mLineHighLightMax, mfHighLightMax - 1.0f);
}

void System_HistoryGraph :: ShowHighLightsLimit(const bool & OnOff)
{
	mFlags &= ~2;
	mFlags |= (OnOff)? 2 : 0;
	bool bShowHighLimits((mFlags & 2) != 0);
	mLine_Records[mLineHighLightMin].mbEnabled = bShowHighLimits;
	mLine_Records[mLineHighLightMax].mbEnabled = bShowHighLimits;
}

void System_HistoryGraph :: SetHighLights(const float & Min, const float & Max)
{
	if(Max < 0.0f) return;
	mfHighLightMin = Min;
	mfHighLightMax = Min + Max;
	SetLine(mLineHighLightMin, mfHighLightMin);
	SetLine(mLineHighLightMax, mfHighLightMax - 1.0f);
}

void System_HistoryGraph :: SetDimension(const int & Width, const int & Height)
{
	mWindowView.x2 = Width;
	mWindowView.y2 = Height;

	int xStart = -(Width >> 1) + mPosition.x;
	mLine[0].x = xStart;
	mLine[0].y = 0;
	mLine[1].x = xStart + (Width - 1);
	mLine[1].y = 0;
}

int System_HistoryGraph :: AddLine(const float & Pos, COLOR Color)
{
	mLine_Records.push_back(LineRecord(true, Pos + mPosition.y, Color));
	return static_cast<int>(mLine_Records.size() - 1);
}

int System_HistoryGraph :: AddGraph(COLOR Color)
{
	mGraph_Records.push_back(GraphRecrod(mWindowView.x2, Color, mPosition));
	return static_cast<int>(mGraph_Records.size() - 1);
}

void System_HistoryGraph :: Parse(const std :: string & Input)
{
	if(System_Utility::LowerCase(Input) == "on")
		mbActive = true;
	else if (System_Utility::LowerCase(Input) == "off")
		mbActive = false;
}

void System_HistoryGraph :: Render()
{
	int Left = 0; 
	size_t Used = 0;
	hgeVertex * Array = g_pSystem_Main->HGESYSTEM()->Gfx_StartBatch(HGEPRIM_LINES, 0, BLEND_DEFAULT, &Left);
	
	LineRecord * Record = NULL;
	for(size_t i = 0; i < mLine_Records.size(); i++)
	{
		Record = &mLine_Records[i];
		if(!Record->mbEnabled) continue;
		Array[Used].x = mLine[0].x;
		Array[Used].y = Record->mfPos;
		Array[Used].col = Record->mColor;
		Used++;
		Array[Used].x = mLine[1].x;
		Array[Used].y = Record->mfPos;
		Array[Used].col = Record->mColor;
		Used++;
	}
	Record = NULL;


	GraphRecrod * GRecord = NULL;
	for(size_t i = 0; i < mGraph_Records.size(); i++)
	{
		GRecord = &mGraph_Records[i];
		memcpy(Array + Used, &GRecord->mVertices[0], GRecord->mVertices.size() * sizeof(hgeVertex));
		Used += GRecord->mVertices.size();
	}
	g_pSystem_Main->HGESYSTEM()->Gfx_FinishBatch(static_cast<int>(Used >> 1));
}
